package wdevent

import (
	"sync"
	"time"
)

type evententity struct {
	event     func(nowtime int64)
	latetime  int64
	cycletime int64
	cyclestat bool
}

type timeevent struct {
	entitylist sync.Map
	onoff      bool
}

//新建定时事件，cycletime 为轮询时间
func NewTimeEvent(cycletime time.Duration) T_Event {
	te := &timeevent{
		entitylist: sync.Map{},
		onoff:      true,
	}
	te.startTiming(cycletime)
	return te
}

func (te *timeevent) startTiming(cycletime time.Duration) {
	go func() {
		for te.onoff {
			t := <-time.After(cycletime)
			nowtime := t.UnixNano()
			eventptr := new(evententity)
			te.entitylist.Range(func(key, value interface{}) bool {
				eventptr = value.(*evententity)
				if nowtime >= eventptr.latetime+eventptr.cycletime {
					eventptr.event(nowtime)
					if !eventptr.cyclestat {
						te.entitylist.Delete(key)
					} else {
						eventptr.latetime = nowtime
					}
				}
				return true
			})
		}
	}()
}

func (t *timeevent) AddEvent(key string, cycletime int64, stat bool, call func(nowtime int64)) {
	ee := &evententity{
		event:     call,
		latetime:  time.Now().UnixNano(),
		cycletime: cycletime,
		cyclestat: stat,
	}
	t.entitylist.Store(key, ee)
}

func (t *timeevent) RemoveEvent(key string) {
	t.entitylist.Delete(key)
}

func (t *timeevent) Stop() {
	t.onoff = false
}
func (t *timeevent) Clear() {
	t.entitylist.Range(func(key, value interface{}) bool {
		t.entitylist.Delete(key)
		return true
	})
}
